# GF_PY3_WORKFLOW_AI_Agent_Python_PPTX.py
# Create by GF 2025-04-02 11:38

# Python 3 Standard Libraries.
import re
import time
# ..................................................
import ollama
import requests

# ##################################################
# Basic Functions

def Text_Opr_Content_in_Mark_Extract(Text:str, Mark_Start:str, Mark_End:str, With_Mark:int=1) -> str:

    # Text Operation - Extract The Content in Mark
    #
    # >>> Text = "Here is The Code:\n\n<CODE_START>\nDESCRIBE example_table;\n<CODE_END>"
    # >>> print(Text)
    # Here is The Code:
    #
    # <CODE_START>
    # DESCRIBE example_table;
    # <CODE_END>
    # >>>
    # >>> Content_in_Mark = Text_Opr_Content_in_Mark_Extract(Text, "<CODE_START>\n", "<CODE_END>", 1)
    # >>> print(Content_in_Mark)
    # <CODE_START>
    # DESCRIBE example_table;
    # <CODE_END>
    # >>> Content_in_Mark = Text_Opr_Content_in_Mark_Extract(Text, "<CODE_START>\n", "<CODE_END>", 0)
    # >>> print(Content_in_Mark)
    # DESCRIBE example_table;

    Capture:list = [0, 0]
    Founded:list = [0, 0]
    Content_in_Mark:str = ''
    # ..............................................
    for i in range(0, len(Text), 1):
        Slice_Idx_A = i
        Slice_Idx_B = i + len(Mark_Start)
        if (Text[Slice_Idx_A:Slice_Idx_B] == Mark_Start):
            Capture[0] = Slice_Idx_A
            Founded[0] = 1
            break
    # ..............................................
    if (Founded[0] == 0):  # If The "Mark Start" is not Found, Return "Empty Char".
        return Content_in_Mark
    # ..............................................
    for i in range((Capture[0] + len(Mark_Start)), len(Text), 1):
        Slice_Idx_A = i
        Slice_Idx_B = i + len(Mark_End)
        if (Text[Slice_Idx_A:Slice_Idx_B] == Mark_End):
            Capture[1] = Slice_Idx_B
            Founded[1] = 1
            break
    # ..............................................
    if (With_Mark == 0):
        Capture[0] = Capture[0] + len(Mark_Start)
        Capture[1] = Capture[1] - len(Mark_End)
    # ..............................................
    Content_in_Mark = Text[Capture[0]:Capture[1]]
    # ..............................................
    return Content_in_Mark

def Chat_for_Multiple_Rounds(Model, Message_List:str):

    # Message_List 应包含:
    # [
    #     {"role":      "user", "content": "Hello!"},
    #     {"role": "assistant", "content": "Hello, I am an AI assistant!"},
    #     {"role":      "user", "content": "What time is it?"},
    #     ......
    # ]
    # ..............................................
    # 调用 Ollama 模型生成回复
    Model_Response = ollama.chat(model=Model, messages=Message_List)
    # ..............................................
    # 获取模型生成内容: Model_Response.get("message").get("content")
    return Model_Response

def Requests_POST_Ollama_0_6_Chat_for_Multiple_Rounds(Model:str, Message_List:list) -> dict:
    
    # Message_List 应包含:
    # [
    #     {"role":      "user", "content": "Hello!"},
    #     {"role": "assistant", "content": "Hello, I am an AI assistant!"},
    #     {"role":      "user", "content": "What time is it?"},
    #     ......
    # ]
    # ..............................................
    # URL Similar to: http://127.0.0.1:11434/api/chat
    # ..............................................
    # 调用 Ollama 模型生成回复
    URL = "http://127.0.0.1:11434/api/chat"
    Rqs_JSON = {"model": Model, "messages":Message_List, "stream":False}
    # ..............................................
    Response = requests.post(url=URL, json=Rqs_JSON)
    # ..............................................
    Rsp_JSON = Response.json()
    # ..............................................
    # 获取模型响应:
    # - Rsp_Message = Rsp_JSON.get("message", {})
    # - Rsp_Content = Rsp_Message["content"]
    return Rsp_JSON

def Requests_POST_API_AI_Agent_Python_PPTX_Code_Exec(Args:list) -> dict:

    URL = "http://127.0.0.1:5000/api/ai-agent-python-pptx-code-exec"
    Rqs_Headers = {"Content-Type": "application/json"}
    Rqs_JSON    = {"args": Args}
    # ..............................................
    Response = requests.post(url=URL, headers=Rqs_Headers, json=Rqs_JSON)
    # ..............................................
    Rsp_JSON = Response.json()
    # ..............................................
    return Rsp_JSON

# ##################################################
# Step by Step Functions

def AI_Agent_Python_PPTX_Common(User_Content:str) -> str:

    Message_List:list = []
    # ..............................................
    Message_List.append({"role": "user", "content": User_Content})
    # ..............................................
    Rsp_JSON = Requests_POST_Ollama_0_6_Chat_for_Multiple_Rounds("deepseek-r1:1.5b", Message_List)
    Rsp_Mesg = Rsp_JSON.get("message", {})
    # ..............................................
    return Rsp_Mesg["content"]

def AI_Agent_Python_PPTX_Consider_Task_Type(User_Content:str) -> str:

    Message_List:list = []
    # ..............................................
    Message_List.append({"role": "user",      "content": "你正在 **通过用户的消息选择接下来的工作类容**, 返回相应的 **任务编号**"})
    Message_List.append({"role": "assistant", "content": "好的"})
    Long_Content = str('\n').join([
        """任务编号及任务内容:""",
        """0. 如果与下列任务无关, 回复数字 [0]""",
        """1. 用户请求 PPT 模板信息, 回复数字 [1]""",
        """2. 用户请求制作 (生成) PPT, 回复数字 [2]""",
        """3. 用户请求修改 PPT, 回复数字 [3]"""
    ])
    Message_List.append({"role": "user",      "content": Long_Content})
    Message_List.append({"role": "assistant", "content": "好的, 我们现在共有 4 种任务类型, 其中 3 种与 PPT 工作相关"})
    # ..............................................
    Message_List.append({"role": "user",      "content": "我需要做一个产品发布会的 PPT"})
    Message_List.append({"role": "assistant", "content": "2"})
    Message_List.append({"role": "user",      "content": "请给我一个科技感强的 PPT 模板"})
    Message_List.append({"role": "assistant", "content": "1"})
    Message_List.append({"role": "user",      "content": "如何导出高清 PDF?"})
    Message_List.append({"role": "assistant", "content": "0"})
    Message_List.append({"role": "user",      "content": "帮我调整这个 PPT 的字体和配色"})
    Message_List.append({"role": "assistant", "content": "3"})
    # ..............................................
    Message_List.append({"role": "user",      "content": User_Content})
    # ..............................................
    Rsp_JSON = Requests_POST_Ollama_0_6_Chat_for_Multiple_Rounds("deepseek-r1:1.5b", Message_List)
    Rsp_Mesg = Rsp_JSON.get("message", {})
    # ..............................................
    return Rsp_Mesg["content"]

def AI_Agent_Python_PPTX_Consider_PPT_Template(User_Content:str, BASE_URL_RESOURCE:str) -> str:

    Message_List:list = []
    # ..............................................
    Message_List.append({"role": "user",      "content": "你正在为用户提供 PPT 模板信息及预览"})
    Message_List.append({"role": "assistant", "content": "好的"})
    Long_Content = str('\n').join([
        """这些是已有并且可用的 PPT 模板:""",
        """[{"name": "潘通蓝时尚简洁", "color": "蓝,白", "style": "商务,简约", "url": "::BASE_URL_RESOURCE::/office.ppt.template.ptlssjj.0.example.600.338.4.jpg"}]"""
    ])
    Message_List.append({"role": "user",      "content": Long_Content.replace("::BASE_URL_RESOURCE::", BASE_URL_RESOURCE)})
    Message_List.append({"role": "assistant", "content": "好的, 我们共有 1 个 PPT 模板"})
    Message_List.append({"role": "user",      "content": "你将以 **![describe](link)** 这种形式将 PPT 模板中的 URL 图像展现给用户"})
    Message_List.append({"role": "assistant", "content": "好的, 我将以 Markdown 图片链接的形式将 PPT 模板中的 URL 图像展现给用户"})
    # ..............................................
    Message_List.append({"role": "user",      "content": "请给出 1 个蓝白色系的商务 PPT 模板"})
    Long_Content = str('\n').join([
        """![潘通蓝时尚简洁模板](::BASE_URL_RESOURCE::/office.ppt.template.ptlssjj.0.example.600.338.4.jpg)""",
        """模板名称: 潘通蓝时尚简洁""",
        """视觉系统: 蓝 + 白 / 时尚 / 简洁""",
        """专业功能: 数据联动更新""",
        """智能组件: SWOT 分析自动生成器""",
        """适用场景: 工作计划"""
    ])
    Message_List.append({"role": "assistant", "content": Long_Content.replace("::BASE_URL_RESOURCE::", BASE_URL_RESOURCE)})
    # ..............................................
    Message_List.append({"role": "user",      "content": User_Content})
    # ..............................................
    Rsp_JSON = Requests_POST_Ollama_0_6_Chat_for_Multiple_Rounds("deepseek-r1:1.5b", Message_List)
    Rsp_Mesg = Rsp_JSON.get("message", {})
    # ..............................................
    return Rsp_Mesg["content"]

def AI_Agent_Python_PPTX_Consider_PPT_Outline_with_Msg_Hist(User_Content:str, Message_Hist:list = []) -> list:

    if (Message_Hist == []):
        Message_List:list = []
        # ..........................................
        Message_List.append({"role": "user",      "content": "你正在为用户输出 **PPT (PowerPoint) 大纲**, 并放在 ```outline\n``` 中"})
        Message_List.append({"role": "assistant", "content": "好的"})
        Message_List.append({"role": "user",      "content": "PPT 大纲中需要明确字体大小 (Font Size)、文字的对齐方式 (Align)、是否应有图表 (Chart)"})
        Message_List.append({"role": "assistant", "content": "好的"})
        Message_List.append({"role": "user",      "content": "可以提醒用户复制你的 PPT 大纲, 根据用户自己的需求修改后重新发送给你"})
        Message_List.append({"role": "assistant", "content": "好的, 我会参考用户重新发送给我的 PPT 大纲, 以便后续在同类任务中表现得更加出色"})
        Long_Content = str('\n').join([
            """请帮我制作 2 页 PPT, 其中一页是封面, 另一页是内容""",
            """封面中包含: 2025 年工作计划、汇报人苟风""",
            """内容中包含: 设计与开发工作是 2025 年的主要工作, 将持续进行 UI 创新"""
        ])
        Message_List.append({"role": "user",      "content": Long_Content})
        Long_Content = str('\n').join([
            """```outline""",
            """1. PPT 封面""",
            """   - 主标题: 2025 年工作计划 (字体大小 48 pt, 居中对齐)""",
            """   - 次级标题: 汇报人 苟风 (字体大小 24 pt, 居中对齐)""",
            """2. PPT 内容 (设计与开发)""",
            """   - 主标题: 设计与开发 (字体大小 24 pt, 左对齐)""",
            """   - 文本内容: 设计与开发工作是 2025 年的主要工作, 将持续进行 UI 创新 (字体大小 16 pt, 左对齐)""",
            """   - 图表内容: 设计工作占比 0.6, 开发工作占比 0.4 (饼图)""",
            """```"""
        ])
        Message_List.append({"role": "assistant", "content": Long_Content})
        Message_List.append({"role": "user",      "content": User_Content})
        # ..........................................
        Rsp_JSON = Requests_POST_Ollama_0_6_Chat_for_Multiple_Rounds("deepseek-r1:1.5b", Message_List)
        Rsp_Mesg = Rsp_JSON.get("message", {})
        # ..........................................
        Message_List.append({"role": "assistant", "content": Rsp_Mesg["content"]})
        # ..........................................
        return Message_List
    else:
        Message_List:list = Message_Hist
        # ..........................................
        Message_List.append({"role": "user",      "content": User_Content})
        # ..........................................
        Rsp_JSON = Requests_POST_Ollama_0_6_Chat_for_Multiple_Rounds("deepseek-r1:1.5b", Message_List)
        Rsp_Mesg = Rsp_JSON.get("message", {})
        # ..........................................
        Message_List.append({"role": "assistant", "content": Rsp_Mesg["content"]})
        # ..........................................
        return Message_List

def AI_Agent_Python_PPTX_Consider_Code_with_Msg_Hist(User_Content:str, PPTX_SAVE_PATH, Message_Hist:list = []) -> list:

    if (Message_Hist == []):
        Message_List:list = []
        # ..........................................
        Message_List.append({"role": "user",      "content": "你正在帮助用户编写 python-pptx 代码, 并放在 ```python\n``` 中"})
        Message_List.append({"role": "assistant", "content": "好的"})
        Message_List.append({"role": "user",      "content": "编写的 python-pptx 代码, 最后生成的 PPT 文件保存路径应为 %s" % PPTX_SAVE_PATH})
        Message_List.append({"role": "assistant", "content": "好的"})
        Long_Content = str('\n').join([
            """这些是已有并且可用的 PPT 素材:""",
            """[{"name": "潘通蓝时尚简洁", "page": "封面", "path": "./resource/office.ppt.template.ptlssjj.1.cover.1280.720.jpg"},""",
            """ {"name": "潘通蓝时尚简洁", "page": "目录", "path": "./resource/office.ppt.template.ptlssjj.2.catalog.1280.720.jpg"},""",
            """ {"name": "潘通蓝时尚简洁", "page": "章节", "path": "./resource/office.ppt.template.ptlssjj.2.chapter.1280.720.jpg"},""",
            """ {"name": "潘通蓝时尚简洁", "page": "内容", "path": "./resource/office.ppt.template.ptlssjj.4.content.1280.720.jpg"}]"""
        ])
        Message_List.append({"role": "user",      "content": Long_Content})
        Message_List.append({"role": "assistant", "content": "好的"})
        Long_Content = str('\n').join([
            """这些是已有并且可用的 PPT 素材各页面的文本定位:""",
            """[{"name": "潘通蓝时尚简洁", "page": "封面", "title_zone": [[0.20,0.33],[0.80,0.48]], "sub_title_zone": [[0.33,0.62],[0.66,0.66]], "text_zone": [[0.20,0.50],[0.80,0.57]]},""",
            """ {"name": "潘通蓝时尚简洁", "page": "目录", "title_zone": [],                        "sub_title_zone": [],                        "text_zone": [[0.51,0.15],[0.90,0.85]]},""",
            """ {"name": "潘通蓝时尚简洁", "page": "章节", "title_zone": [[0.15,0.48],[0.81,0.57]], "sub_title_zone": [[0.15,0.31],[0.81,0.45]], "text_zone": [[0.14,0.58],[0.86,0.73]]},""",
            """ {"name": "潘通蓝时尚简洁", "page": "内容", "title_zone": [[0.06,0.02],[0.81,0.57]], "sub_title_zone": [],                        "text_zone": [[0.04,0.16],[0.49,0.90]]}]""",
            """其中, [[0.20,0.33],[0.80,0.48]] 表示在图像中从左上角 [w, h] 到右下角 [w, h] 的区域定位"""
        ])
        Message_List.append({"role": "user",      "content": Long_Content})
        Message_List.append({"role": "assistant", "content": "好的, 我将在生成 python-pptx 代码时使用这些素材"})
        Long_Content = str('\n').join([
            """请根据以下 PPT 大纲生成 python-pptx 代码:""",
            """1. PPT 封面""",
            """   - 主标题: 2025 年工作计划 (字体大小 48 pt, 居中对齐)""",
            """   - 次级标题: 汇报人 苟风 (字体大小 24 pt, 居中对齐)""",
            """2. PPT 内容 (设计与开发)""",
            """   - 主标题: 设计与开发 (字体大小 24 pt, 左对齐)""",
            """   - 文本内容: 设计与开发工作是 2025 年的主要工作, 将持续进行 UI 创新 (字体大小 16 pt, 左对齐)""",
            """   - 图表内容: 设计工作占比 0.6, 开发工作占比 0.4 (饼图)"""
        ])
        Message_List.append({"role": "user",      "content": Long_Content})
        Long_Content = str('\n').join([
            """```python""",
            """from pptx import Presentation""",
            """from pptx.util import Pt""",
            """from pptx.enum.text import PP_ALIGN""",
            """from pptx.chart.data import ChartData""",
            """from pptx.enum.chart import XL_CHART_TYPE""",
            """ """,
            """# 创建演示文稿""",
            """prs = Presentation()""",
            """ """,
            """# 1. 添加封面页""",
            """cover_slide_layout = prs.slide_layouts[6]  # 使用空白布局""",
            """cover_slide = prs.slides.add_slide(cover_slide_layout)""",
            """ """,
            """# 添加封面背景图片""",
            """img_path = \"./resource/office.ppt.template.ptlssjj.1.cover.1280.720.jpg\"""",
            """cover_slide.shapes.add_picture(img_path, 0, 0, prs.slide_width, prs.slide_height)""",
            """ """,
            """# 添加主标题""",
            """title_box = cover_slide.shapes.add_textbox(""",
            """    left=prs.slide_width * 0.20,""",
            """    top=prs.slide_height * 0.33,""",
            """    width=prs.slide_width * 0.60,""",
            """    height=prs.slide_height * 0.15""",
            """)""",
            """title = title_box.text_frame""",
            """title.text = \"2025 年工作计划\"""",
            """title.paragraphs[0].font.size = Pt(48)""",
            """title.paragraphs[0].font.bold = True""",
            """title.paragraphs[0].alignment = PP_ALIGN.CENTER""",
            """ """,
            """# 添加次级标题""",
            """subtitle_box = cover_slide.shapes.add_textbox(""",
            """    left=prs.slide_width * 0.33,""",
            """    top=prs.slide_height * 0.62,""",
            """    width=prs.slide_width * 0.33,""",
            """    height=prs.slide_height * 0.04""",
            """)""",
            """subtitle = subtitle_box.text_frame""",
            """subtitle.text = \"汇报人 苟风\"""",
            """subtitle.paragraphs[0].font.size = Pt(24)""",
            """subtitle.paragraphs[0].alignment = PP_ALIGN.CENTER""",
            """ """,
            """# 2. 添加内容页(设计与开发)""",
            """content_slide_layout = prs.slide_layouts[6]  # 使用空白布局""",
            """content_slide = prs.slides.add_slide(content_slide_layout)""",
            """ """,
            """# 添加内容页背景图片""",
            """img_path = \"./resource/office.ppt.template.ptlssjj.4.content.1280.720.jpg\"""",
            """content_slide.shapes.add_picture(img_path, 0, 0, prs.slide_width, prs.slide_height)""",
            """ """,
            """# 添加主标题""",
            """title_box = content_slide.shapes.add_textbox(""",
            """    left=prs.slide_width * 0.06,""",
            """    top=prs.slide_height * 0.02,""",
            """    width=prs.slide_width * 0.75,""",
            """    height=prs.slide_height * 0.55""",
            """)""",
            """title = title_box.text_frame""",
            """title.text = \"设计与开发\"""",
            """title.paragraphs[0].font.size = Pt(24)""",
            """title.paragraphs[0].alignment = PP_ALIGN.LEFT""",
            """ """,
            """# 添加文本内容""",
            """text_box = content_slide.shapes.add_textbox(""",
            """    left=prs.slide_width * 0.04,""",
            """    top=prs.slide_height * 0.16,""",
            """    width=prs.slide_width * 0.45,""",
            """    height=prs.slide_height * 0.74""",
            """)""",
            """text_frame = text_box.text_frame""",
            """text_frame.text = \"设计与开发工作是 2025 年的主要工作, 将持续进行 UI 创新\"""",
            """text_frame.paragraphs[0].font.size = Pt(16)""",
            """text_frame.paragraphs[0].alignment = PP_ALIGN.LEFT""",
            """ """,
            """# 添加饼图""",
            """chart_data = ChartData()""",
            """chart_data.categories = ['设计工作', '开发工作']""",
            """chart_data.add_series('占比', (0.6, 0.4))""",
            """ """,
            """x, y, cx, cy = prs.slide_width * 0.55, prs.slide_height * 0.2, prs.slide_width * 0.4, prs.slide_height * 0.6""",
            """chart = content_slide.shapes.add_chart(""",
            """    XL_CHART_TYPE.PIE, x, y, cx, cy, chart_data""",
            """).chart""",
            """ """,
            """chart.has_legend = True""",
            """chart.plots[0].has_data_labels = True""",
            """ """,
            """# 保存PPT文件""",
            """prs.save('/www/html/1746456033.3503273.pptx')""",
            """```"""
        ])
        Message_List.append({"role": "assistant", "content": Long_Content})
        # ..........................................
        Message_List.append({"role": "user",      "content": User_Content})
        # ..........................................
        Rsp_JSON = Requests_POST_Ollama_0_6_Chat_for_Multiple_Rounds("deepseek-r1:1.5b", Message_List)
        Rsp_Mesg = Rsp_JSON.get("message", {})
        # ..........................................
        Message_List.append({"role": "assistant", "content": Rsp_Mesg["content"]})
        # ..........................................
        return Message_List
    else:
        Message_List:list = Message_Hist
        # ..........................................
        Message_List.append({"role": "user",      "content": User_Content})
        # ..........................................
        Rsp_JSON = Requests_POST_Ollama_0_6_Chat_for_Multiple_Rounds("deepseek-r1:1.5b", Message_List)
        Rsp_Mesg = Rsp_JSON.get("message", {})
        # ..........................................
        Message_List.append({"role": "assistant", "content": Rsp_Mesg["content"]})
        # ..........................................
        return Message_List

# ##################################################
# Workflow Functions

def Workflow(User_Content):

    BASE_URL_RESOURCE = "http://127.0.0.1/resource"
    PPTX_SAVE_PATH    = "/default/path/%s.pptx" % str(time.time())
    # ..............................................
    Reconsider_PPT_Outline_Count:int = 3
    Reconsider_Code_Count:int        = 3
    Re_Execute_Code_Count:int        = 3

    # **********************************************

    try:
        Considered_Task_Type = AI_Agent_Python_PPTX_Consider_Task_Type(User_Content)
        # ..............................................
        Considered_Task_Type = re.findall("0|1|2|3", Considered_Task_Type)[0]
        # ..............................................
        print("[Workflow] Working in AI Agent Python PPTX -> Considering Task Type (1)")
    except Exception as e:
        Considered_Task_Type = '0'
        print("[Workflow] Working in AI Agent Python PPTX -> Considering Task Type (0)")
        print(e)
    
    # **********************************************
    
    if (Considered_Task_Type == '0'):

        print("[Workflow] Working in AI Agent Python PPTX -> Common Conversation (1)")
        Rsp_Ctnt = AI_Agent_Python_PPTX_Common(User_Content)
        return """{"role": "assistant", "content": "%s"}""" % Rsp_Ctnt.replace('\n', '\\n')
    
    # **********************************************
    
    if (Considered_Task_Type == '1'):

        print("[Workflow] Working in AI Agent Python PPTX -> Considering PPT Template (1)")
        Rsp_Ctnt = AI_Agent_Python_PPTX_Consider_PPT_Template(User_Content, BASE_URL_RESOURCE)
        return """{"role": "assistant", "content": "%s"}""" % Rsp_Ctnt.replace('\n', '\\n')
    
    # **********************************************
    
    if (Considered_Task_Type == '2' or Considered_Task_Type == '3'):
    
        Msg_List = AI_Agent_Python_PPTX_Consider_PPT_Outline_with_Msg_Hist(User_Content, Message_Hist=[])
        # ..........................................
        Considered_PPT_Outline = Text_Opr_Content_in_Mark_Extract(Msg_List[-1]["content"], "```outline\n", "```", With_Mark=0)
        # ..........................................
        i = 1
        while (Considered_PPT_Outline == '' and i <= Reconsider_PPT_Outline_Count):
            Msg_List = AI_Agent_Python_PPTX_Consider_PPT_Outline_with_Msg_Hist("你的响应中没有 ```outline\n``` 包裹的 PPT 大纲, 请重新响应", Message_Hist=Msg_List)
            # ......................................
            Considered_PPT_Outline = Text_Opr_Content_in_Mark_Extract(Msg_List[-1]["content"], "```outline\n", "```", With_Mark=0)
            # ......................................
            i = i + 1
        # ..........................................
        print("[Workflow] Working in AI Agent Python PPTX -> Considering PPT Outline (1)")

        # ------------------------------------------

        Msg_List = AI_Agent_Python_PPTX_Consider_Code_with_Msg_Hist(("请根据以下 PPT 大纲生成 python-pptx 代码\n%s" % Considered_PPT_Outline), PPTX_SAVE_PATH, Message_Hist=[])
        # ..........................................
        Considered_Code = Text_Opr_Content_in_Mark_Extract(Msg_List[-1]["content"], "```python\n", "```", With_Mark=0)
        # ..........................................
        i = 1
        while (Considered_Code == '' and i <= Reconsider_Code_Count):
            Msg_List = AI_Agent_Python_PPTX_Consider_Code_with_Msg_Hist("你的响应中没有 ```python\n``` 包裹的 python-pptx 代码, 请重新响应", PPTX_SAVE_PATH, Message_Hist=Msg_List)
            # ......................................
            Considered_Code = Text_Opr_Content_in_Mark_Extract(Msg_List[-1]["content"], "```python\n", "```", With_Mark=0)
            # ......................................
            i = i + 1
        # ..........................................
        i = 1
        while (Considered_Code != '' and i <= Reconsider_Code_Count and PPTX_SAVE_PATH not in Considered_Code):
            Msg_List = AI_Agent_Python_PPTX_Consider_Code_with_Msg_Hist(("你的响应中没有包含指定的输出文件路径: %s, 请重新响应" % PPTX_SAVE_PATH), PPTX_SAVE_PATH, Message_Hist=Msg_List)
            # ......................................
            Considered_Code = Text_Opr_Content_in_Mark_Extract(Msg_List[-1]["content"], "```python\n", "```", With_Mark=0)
            # ......................................
            i = i + 1
        # ..........................................
        print("[Workflow] Working in AI Agent Python PPTX -> Considering python-pptx Code (1)")

        # ------------------------------------------

        Code_Exec_Response = Requests_POST_API_AI_Agent_Python_PPTX_Code_Exec([PPTX_SAVE_PATH, Considered_Code])
        # ..........................................
        i = 1
        while (Code_Exec_Response["status"] == '0' and i <= Re_Execute_Code_Count):
            Msg_List = AI_Agent_Python_PPTX_Consider_Code_with_Msg_Hist(("生成的 python-pptx 执行出错了: %s, 请重新响应" % Code_Exec_Response["error"]), PPTX_SAVE_PATH, Message_Hist=Msg_List)
            # ......................................
            Considered_Code = Text_Opr_Content_in_Mark_Extract(Msg_List[-1]["content"], "```python\n", "```", With_Mark=0)
            # ..........................................
            Code_Exec_Response = Requests_POST_API_AI_Agent_Python_PPTX_Code_Exec([PPTX_SAVE_PATH, Considered_Code])
            # ......................................
            i = i + 1
        # ..........................................
        print("[Workflow] Working in AI Agent Python PPTX -> Executing python-pptx Code (1)")

        # ------------------------------------------

        return """{"role": "assistant", "content": "%s\n\n生成的 PPT 文档获取地址: %s"}""" % (Considered_PPT_Outline.replace('\n', '\\n'), Code_Exec_Response["pptx"])

    # **********************************************

    return """{"role": "assistant", "content": "服务器繁忙, 请稍后重试"}"""

# EOF Signed by GF.
